# app/worker/tasks_worker.py
import time
import logging

from app.core.database import SessionLocal
from app.models.base_model import TaskList as AsyncTask
from datetime import datetime
from app.api.v2.wcs.device_services_base import DeviceServicesBase

# 配置日志
logging.basicConfig(level=logging.INFO)
logger = logging.getLogger(__name__)

service = DeviceServicesBase()

class ORMTaskProcessor:
    def __init__(self):
        self.poll_interval = 1.0
        self.max_interval = 60.0
        self.backoff_factor = 1.5

    def fetch_pending_task(self):
        """使用ORM查询获取一个待处理的任务"""
        session = SessionLocal()
        try:
            # 使用ORM的query方法进行查询，这比直接写SQL更安全、更直观
            task = session.query(AsyncTask).filter(
                AsyncTask.status == 'pending'
            ).order_by(AsyncTask.created_at.asc()).with_for_update(skip_locked=True).first()
            # with_for_update(skip_locked=True) 是防止多个Worker同时处理同一个任务的关键（行级锁）

            if task:
                logger.info(f"获取到待处理任务: ID={task.id}, Name={task.name}")
                # 立即更新状态为处理中
                task.status = 'processing'
                task.started_at = datetime.utcnow()
                session.commit()
                return task
            return None
        except Exception as e:
            session.rollback()
            logger.error(f"获取任务时出错: {e}")
            return None
        finally:
            session.close()

    def process_task(self, task):
        """处理单个任务"""
        logger.info(f"开始处理任务 ID: {task.id}")
        session = SessionLocal()

        try:
            # 根据任务名称执行不同的业务逻辑
            if task.name == 'process_image':
                result = process_image_task(eval(task.task_data))  # 假设task_data是字典的字符串表示
            elif task.name == 'generate_report':
                result = generate_report_task(eval(task.task_data))
            else:
                logger.error(f"未知的任务类型: {task.name}")
                result = False

            # 使用ORM更新任务状态
            task_to_update = session.merge(task)  # 将游离态对象重新关联到当前session
            if result:
                task_to_update.status = 'completed'
                task_to_update.result = "Task executed successfully."
            else:
                task_to_update.status = 'failed'
                task_to_update.result = "Task execution failed."
            task_to_update.finished_at = datetime.utcnow()

            session.commit()
            logger.info(f"任务 ID: {task.id} 处理完成，状态: {task_to_update.status}")

        except Exception as e:
            session.rollback()
            logger.error(f"处理任务 ID: {task.id} 时发生异常: {e}")
            # 可以在失败时尝试更新任务状态为失败
            try:
                task_to_update = session.merge(task)
                task_to_update.status = 'failed'
                task_to_update.result = str(e)
                session.commit()
            except Exception as update_error:
                logger.error(f"更新任务失败状态时也出错了: {update_error}")
        finally:
            session.close()

    def run_worker(self):
        """Worker的主循环"""
        logger.info("基于ORM的任务处理器启动...")
        empty_polls = 0

        while True:
            try:
                task = self.fetch_pending_task()

                if task:
                    self.poll_interval = 1.0
                    empty_polls = 0
                    self.process_task(task)
                else:
                    empty_polls += 1
                    sleep_time = min(self.poll_interval, self.max_interval)
                    logger.debug(f"未找到待处理任务，{sleep_time}秒后重新检查...")
                    time.sleep(sleep_time)
                    self.poll_interval *= self.backoff_factor

            except KeyboardInterrupt:
                logger.info("收到中断信号，停止任务处理器...")
                break
            except Exception as e:
                logger.error(f"Worker运行过程中发生未预期错误: {e}")
                time.sleep(5)